package obs;

import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;


public class ManyThreadV3 {
    public static void debug(Object o){
        String s = ""+Thread.currentThread().getName();

        System.out.println(s+" thread: "+o.toString());
    }

    //    public static List<MeiMeiEvent> meiMeiqueue= new ArrayList<>();
    public static SimpleBlockingQueue<MeiMeiEvent> meiMeiqueueToMing = new SimpleBlockingQueue<MeiMeiEvent>();
    public static SimpleBlockingQueue<MeiMeiEvent> meiMeiqueueToZhang = new SimpleBlockingQueue<MeiMeiEvent>();
    public static SyncXiaoMing syncXiaoMing = new SyncXiaoMing();
    public static SyncXiaoZhang syncXiaoZhang = new SyncXiaoZhang();

    public static void main(String[] args) throws InterruptedException {

        new Thread(()-> {
            SyncMeiMei syncMeiMei = new SyncMeiMei();
            Scanner scanner = new Scanner(System.in);
            while (true){
                String s = scanner.nextLine();
                Integer r= 0;
                try {
                    r = Integer.parseInt(s);
                }catch (Exception e){
                    r=100;
                }
                syncMeiMei.setAge(r);
                debug("妹妹的年龄　"+syncMeiMei.getAge());
                MeiMeiEvent meiMeiEventM = new MeiMeiEvent(r, System.currentTimeMillis());
                MeiMeiEvent meiMeiEventZ = new MeiMeiEvent(r, System.currentTimeMillis());
                meiMeiqueueToMing.addEx(meiMeiEventM);
                meiMeiqueueToZhang.addEx(meiMeiEventZ);
            }

        },"meimei").start();
        new Thread(()-> {
            while (true){
                MeiMeiEvent event = meiMeiqueueToMing.removeEx();
                updateXiaoming(event);
            }
        },"xiaoming").start();
        new Thread(()-> {
            while (true){
                MeiMeiEvent event = meiMeiqueueToZhang.removeEx();
                updateXiaozhang(event);
            }


        },"xiaozhang").start();
        while (true){
            Thread.sleep(2000);
            meiMeiqueueToZhang.inspectqueue("小张");
            meiMeiqueueToMing.inspectqueue("小明");
        }

//        System.out.println("end");
    }
    public static void updateXiaozhang(MeiMeiEvent meimei){
        try {
            Thread.sleep(6000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        syncXiaoZhang.setAge(meimei.getAge()+6);
        debug("小张年龄　"+syncXiaoZhang.getAge()+" while meimei is "+meimei.getAge());
    }
    public static void updateXiaoming(MeiMeiEvent meimei){
        try {
            Thread.sleep(2000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        syncXiaoMing.setAge(meimei.getAge()+8);
        debug("小明年龄　"+syncXiaoMing.getAge()+" while meimei is "+meimei.getAge());
    }
}

class SimpleBlockingQueue<T>{
    private   List<T> corelist= new ArrayList<>();
    private   ReentrantLock emptylock = new ReentrantLock();
    private   Condition emptyTag = emptylock.newCondition();
    public void addEx(T meiMeiEvent){
        final ReentrantLock lock = this.emptylock;
        lock.lock();
        try{
            // 事件
            corelist.add(meiMeiEvent);
            //通知notify
            emptyTag.signal();
        }finally {
            lock.unlock();
        }
    }
    public T removeEx(){
        final ReentrantLock lock = this.emptylock;
        T event = null;
        lock.lock();
        try{
            while (corelist.size()==0){

                emptyTag.await();
            }
            event= corelist.remove(0);
        } catch (InterruptedException e) {
            e.printStackTrace();
        } finally {
            lock.unlock();
        }
        return event;
    }



    public void inspectqueue(String name){
        final ReentrantLock lock = this.emptylock;
        lock.lock();
        try{
            _debug("妹妹－＞"+name+"queue　："+corelist);
        }finally {
            lock.unlock();
        }
    }
    private void _debug(Object o){
        String s = ""+Thread.currentThread().getName();

        System.out.println(s+" thread: "+o.toString());
    }


}